from alipay import AliPay
import uuid
from django.conf import settings
from django.http import JsonResponse
from django.shortcuts import render
from django.views.generic import View
from rest_framework.views import APIView
import os
def index(request):
    return render(request,'demo.html')

# 处理支付宝回调
class AlipayView(APIView):
    def get(self, request):
        """
        处理支付宝的return_url返回
        """
        processed_dict = {}
        # 获取GET中参数
        for key, value in request.GET.items():
            processed_dict[key] = value
        # 取出sign
        sign = processed_dict.pop("sign", None)
        merchant_private_key_path = open(os.path.join("D:/gitee/Alipy_WX/payments/keys/app_private_key.pem")).read()
        alipay_public_key_path = open(os.path.join("D:/gitee/Alipy_WX/payments/keys/alipay_public_key.pem")).read()
        # 生成ALipay对象
        alipay = AliPay(
            appid="2016102200736331", # APPID
            app_notify_url=None, # 默认回调url,可以传也可以不传
            app_private_key_string=merchant_private_key_path, # 私钥的路径
            alipay_public_key_string=alipay_public_key_path, # 支付宝公钥的路径
            sign_type="RSA2", # RSA 或者 RSA2，签名的算法
            debug = True # 默认False，沙箱环境改成True
        )

        verify_re = alipay.verify(processed_dict, sign)

        # 这里可以不做操作。因为不管发不发return url。notify url都会修改订单状态。
        if verify_re is True:
            order_sn = processed_dict.get('out_trade_no', None)
            trade_no = processed_dict.get('trade_no', None)

            return render(request,'pay_success.html')
        else:
            return render(request,'demo.html')

    def post(self, request):
        """
        处理支付宝的notify_url
        """
        # 先将sign剔除掉
        processed_dict = {}
        for key, value in request.POST.items():
            processed_dict[key] = value

        sign = processed_dict.pop("sign", None)

        merchant_private_key_path = open(os.path.join("D:/gitee/Alipy_WX/payments/keys/app_private_key.pem")).read()
        alipay_public_key_path = open(os.path.join("D:/gitee/Alipy_WX/payments/keys/alipay_public_key.pem")).read()
        # 生成ALipay对象
        alipay = AliPay(
            appid="2016102200736331", # APPID
            app_notify_url=None, # 默认回调url,可以传也可以不传
            app_private_key_string=merchant_private_key_path, # 私钥的路径
            alipay_public_key_string=alipay_public_key_path, # 支付宝公钥的路径
            sign_type="RSA2", # RSA 或者 RSA2，签名的算法
            debug = True # 默认False，沙箱环境改成True
        )

        # 进行验签，确保这是支付宝给我们的
        verify_re = alipay.verify(processed_dict, sign)

        # 如果验签成功
        if verify_re is True:
            order_sn = processed_dict.get('out_trade_no', None) # 商户订单号
            trade_no = processed_dict.get('trade_no', None) # 支付宝交易号
            trade_status = processed_dict.get('trade_status', None) # 交易状态
            # 将success返回给支付宝，支付宝就不会一直不停的继续发消息了。
            return Response("success")


# 生成支付宝支付链接
class OrderPayView(View):
    def post(self,request):
        # 接收参数
        order_id = str(uuid.uuid1())
        merchant_private_key_path = open(os.path.join("D:/gitee/Alipy_WX/payments/keys/app_private_key.pem")).read()
        alipay_public_key_path = open(os.path.join("D:/gitee/Alipy_WX/payments/keys/alipay_public_key.pem")).read()
        # 业务处理:使用Python sdk调用支付宝的支付接口
        alipay = AliPay(
            appid="2016102200736331", # APPID
            app_notify_url=None, # 默认回调url,可以传也可以不传
            app_private_key_string=merchant_private_key_path, # 私钥的路径
            alipay_public_key_string=alipay_public_key_path, # 支付宝公钥的路径
            sign_type="RSA2", # RSA 或者 RSA2，签名的算法
            debug = True # 默认False，沙箱环境改成True
        )
        # 借助alipay对象，向支付宝发起支付请求
        # 电脑网站支付，需要跳转到https://openapi.alipaydev.com/gateway.do?+order_string
        total_pay = 5 #订单总金额
        order_string = alipay.api_alipay_trade_page_pay(
            out_trade_no=order_id,  # 订单id
            total_amount=str(total_pay), # 支付宝总金额
            subject="测试支付", # 订单标题
            return_url="http://127.0.0.1:8000/success/",
            notify_url=None
        )
        # 返回应答
        pay_url = "https://openapi.alipaydev.com/gateway.do?"+order_string
        return JsonResponse({"pay_url":pay_url})


# 查询支付状态
class CheckPayView(View):
    def post(self,request):
        # 初始化
        merchant_private_key_path = open(os.path.join("D:/gitee/Alipy_WX/payments/keys/app_private_key.pem")).read()
        alipay_public_key_path = open(os.path.join("D:/gitee/Alipy_WX/payments/keys/alipay_public_key.pem")).read()
        # 业务处理:使用Python sdk调用支付宝的支付接口
        alipay = AliPay(
            appid="2016102200736331", # APPID
            app_notify_url=None, # 默认回调url,可以传也可以不传
            app_private_key_string=merchant_private_key_path, # 私钥的路径
            alipay_public_key_string=alipay_public_key_path, # 支付宝公钥的路径
            sign_type="RSA2", # RSA 或者 RSA2，签名的算法
            debug = True # 默认False，沙箱环境改成True
        )
        order_id = str(uuid.uuid1()) # 前端传入，目前是随机生成
        while True:
            response = alipay.api_alipay_trade_query(out_trade_no=order_id)
            # out_trade_no和trade_no两个至少有一个存在
            code = response.get("code")
            # 如果返回码为10000和交易状态为交易支付成功
            if code == "10000" and response.get("trade_status") == "TRADE_SUCCESS":
                # 获取支付宝交易号
                trade_no = response.get("trade_no")
                return JsonResponse({"status":"ok","message":"支付成功"})
            # 返回码为40004 或 交易状态为等待买家付款
            elif code == "40004" or (response.get("trade_status") == "WAIT_BUYER_PAY"):
                # 等待买家付款
                import time
                time.sleep(5)
                continue
            else:
                # 支付出错
                return JsonResponse({"status":"error","message":"支付失败"})